package com.bangdream.michelia.tool.retrofithttp;

import android.os.Handler;
import android.os.Looper;
import android.util.Log;


import com.bangdream.michelia.BuildConfig;
import com.bangdream.michelia.utils.MyLog;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.TimeUnit;

import okhttp3.Call;
import okhttp3.Callback;
import okhttp3.FormBody;
import okhttp3.MediaType;
import okhttp3.MultipartBody;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.RequestBody;
import okhttp3.Response;
import okhttp3.logging.HttpLoggingInterceptor;

/**
 * Created by ${火龙裸先生} on 2016/9/28.
 * 邮箱：791335000@qq.com
 * <p/>
 * OKhttpManager OKhttp封装类
 */
public class OKhttpManager{
	private static final String TAG = "OKhttpManager";
    private static OkHttpClient client;
    private static OKhttpManager oKhttpManager;
    private Handler mHandler;

	public static final String TYPE = "application/octet-stream";
    /**
     * 单例获取 OKhttpManager实例
     */
    public static OKhttpManager getInstance() {
        if (oKhttpManager == null) {
            oKhttpManager = new OKhttpManager();
        }
        return oKhttpManager;
    }
    public static OkHttpClient getOkHttpClient() {
        if (client == null) {
            client = new OkHttpClient.Builder()
                    .writeTimeout(20,TimeUnit.SECONDS)//设置写的超时时间
                    .connectTimeout(20, TimeUnit.SECONDS)//设置连接超时时间
                    .readTimeout(20, TimeUnit.SECONDS)//设置读取超时时间
                    .build();
        }
        return client;
    }

    private OKhttpManager() {
        //client = new OkHttpClient();
        client = new OkHttpClient.Builder()
				.writeTimeout(100,TimeUnit.SECONDS)//设置写的超时时间
				.connectTimeout(100, TimeUnit.SECONDS)//设置连接超时时间
				.readTimeout(100, TimeUnit.SECONDS)//设置读取超时时间
				.build();
		mHandler = new Handler(Looper.getMainLooper());
    }
	private void setCookic(String url,String cookie,final DataCallBack callBack)
	{
		String returnData=null;
		Request request = new Request.Builder()
				.addHeader("cookie", cookie)
				.url(url)
				.removeHeader("User-Agent")
				.build();
		Response response = null;
			//response = client.newCall(request).execute();
			client.newCall(request).enqueue(new Callback() {
				@Override
				public void onFailure(Call call, IOException e) {
					deliverDataFailure(call, e, callBack);
				}

				@Override
				public void onResponse(Call call, Response response) {
					try {
						String result = response.body().string();
						deliverDataSuccess(result, callBack);
					} catch (IOException e) {
						deliverDataFailure(call, e, callBack);
					}
				}
			});
			//returnData=response.body().string();
			//Log.i("ss", "url is " + url + "_______RETUNRN DATA IS " + returnData);
	}

    /**************
     * 内部逻辑处理
     ****************/
    private Response p_getSync(String url) throws IOException {
        Request request = new Request.Builder().url(url).build();
        Response response = client.newCall(request).execute();
        return response;
    }

    private String p_getSyncAsString(String url) throws IOException {
        return p_getSync(url).body().string();
    }
    private void p_getAsync(String url, final DataCallBack callBack) {
        final Request request = new Request.Builder().url(url)
				.removeHeader("User-Agent").addHeader("User-Agent",
						"android")
				.build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                deliverDataFailure(call, e, callBack);
            }

            @Override
            public void onResponse(Call call, Response response) {
                try {
                    String result = response.body().string();
                    deliverDataSuccess(result, callBack);
                } catch (IOException e) {
                    deliverDataFailure(call, e, callBack);
                }
            }
        });
    }
	//普通post请求
    private void p_postAsync(String url, Map<String, String> params, final DataCallBack callBack) {
        RequestBody requestBody = null;

        if (params == null) {
            params = new HashMap<String, String>();
        }
        FormBody.Builder builder = new FormBody.Builder();
        for (Map.Entry<String, String> entry : params.entrySet()) {
            String key = entry.getKey().toString();
            String value = null;
            if (entry.getValue() == null) {
                value = "";
            } else {
                value = entry.getValue().toString();
            }
            builder.add(key, value);
        }
        requestBody = builder.build();
        final Request request = new Request.Builder().url(url).post(requestBody)
				.removeHeader("User-Agent").addHeader("User-Agent",
				"android")
				.build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                deliverDataFailure(call, e, callBack);
            }

            @Override
            public void onResponse(Call call, Response response) throws IOException {
                try {
                    String result = response.body().string();
                    deliverDataSuccess(result, callBack);
                } catch (IOException e) {
                    deliverDataFailure(call, e, callBack);
                }
            }
        });
    }
	//普通post请求 设置cookie
    private void p_postAsyncCookie(String url,String cookie, Map<Object, Object> params, final DataCallBack callBack) {

		RequestBody requestBody = null;

		if (params == null) {
			params = new HashMap<Object, Object>();
		}
		FormBody.Builder builder = new FormBody.Builder();
		for (Map.Entry<Object, Object> entry : params.entrySet()) {
			String key = entry.getKey().toString();
			String value = null;
			if (entry.getValue() == null) {
				value = "";
			} else {
				value = entry.getValue().toString();
			}
			builder.add(key, value);
		}
		requestBody = builder.build();
		final Request request = new Request.Builder().url(url).post(requestBody).addHeader("cookie", cookie)
				.removeHeader("User-Agent").addHeader("User-Agent",
						"android")
				.build();
		client.newCall(request).enqueue(new Callback() {
			@Override
			public void onFailure(Call call, IOException e) {
				deliverDataFailure(call, e, callBack);
			}

			@Override
			public void onResponse(Call call, Response response) throws IOException {
				try {
					String result = response.body().string();
					deliverDataSuccess(result, callBack);
				} catch (IOException e) {
					deliverDataFailure(call, e, callBack);
				}
			}
		});
    }

	//上传文件post请求
    private void p_postAsyncFile(String url,String cookie, Map<String, String> params, Map<String, File> paramsFile, final DataCallBack callBack) {
		MultipartBody.Builder requestBody = null;

        if (params == null) {
            params = new HashMap<String, String>();
        }
		if (paramsFile == null) {
			paramsFile = new HashMap<String, File>();
        }

		requestBody = new MultipartBody.Builder().setType(MultipartBody.FORM);
		if(params!=null)
		{
			for (Map.Entry entry : params.entrySet()) {
				requestBody.addFormDataPart(String.valueOf(entry.getKey()), String.valueOf(entry.getValue()));
			}
		}
		if(paramsFile != null){
			for (Map.Entry<String,File> entry : paramsFile.entrySet()) {
				// MediaType.parse() 里面是上传的文件类型。
				RequestBody body = RequestBody.create(MediaType.parse(TYPE), entry.getValue());
				String filename = entry.getValue().getName();
				// 参数分别为， 请求key ，文件名称 ， RequestBody
				requestBody.addFormDataPart(entry.getKey(), entry.getValue().getName(), body);
			}
		}

        final Request request = new Request.Builder().addHeader("cookie", cookie)
				.url(url).post(requestBody.build())
				.removeHeader("User-Agent").addHeader("User-Agent",
				"android")
				.build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                deliverDataFailure(call, e, callBack);
            }

            @Override
            public void onResponse(Call call, Response response) throws IOException {
                try {
                    String result = response.body().string();
                    deliverDataSuccess(result, callBack);
                } catch (IOException e) {
                    deliverDataFailure(call, e, callBack);
                }
            }
        });
    }


	/**
	 *	下载文件post请求
	 * @param fileUrl		文件url
	 * @param cookie		用户cookie
	 * @param destFileDir  存储目标目录
	 * @param callBack		成功失败的回调函数
	 */
    private void p_postDownLoadFile(final String fileUrl, String cookie, final String destFileDir, final DataCallBack callBack) {
		final File file = new File(destFileDir);
		if (file.exists()) {
			//successCallBack((T) file, callBack);
			return;
		}
		MyLog.d(TAG,"fileUrl==="+fileUrl);
		MyLog.d(TAG,"destFileDir==="+destFileDir);
		MyLog.d(TAG,"cookie===="+cookie);
        final Request request = new Request.Builder().addHeader("cookie", cookie)
				.url(fileUrl)
				.removeHeader("User-Agent").addHeader("User-Agent",
				"android")
				.build();
        client.newCall(request).enqueue(new Callback() {
            @Override
            public void onFailure(Call call, IOException e) {
                deliverDataFailure(call, e, callBack);
            }
            @Override
            public void onResponse(Call call, Response response) throws IOException {
				InputStream is = null;
				byte[] buf = new byte[2048];
				int len = 0;
				FileOutputStream fos = null;
				try {
					long total = response.body().contentLength();
					Log.e(TAG, "total------>" + total);
					long current = 0;
					is = response.body().byteStream();
					fos = new FileOutputStream(file);
					while ((len = is.read(buf)) != -1) {
						current += len;
						fos.write(buf, 0, len);
						Log.e(TAG, "current------>" + current);
						//progressCallBack(total, current, callBack);
					}
					fos.flush();
					deliverDataSuccess(destFileDir, callBack);
				} catch (IOException e) {
					deliverDataFailure(call, e, callBack);
				}finally {
					try {
						if (is != null) {
							is.close();
						}
						if (fos != null) {
							fos.close();
						}
					} catch (IOException e) {
						Log.e(TAG, e.toString());
					}
				}
            }
        });
    }

    /**
     * 数据分发的方法
     */
    private void deliverDataFailure(final Call call, final IOException e, final DataCallBack callBack) {
        mHandler.post(new Runnable() {
            @Override
            public void run() {
                if (callBack != null) {
                    callBack.requestFailure(call, e);
                }
            }
        });
    }

    private void deliverDataSuccess(final String result, final DataCallBack callBack) {
        mHandler.post(new Runnable() {
            @Override
            public void run() {
                if (callBack != null) {
                    callBack.requestSuccess(result);
                }
            }
        });
    }


    /******************
     * 对外公布的方法
     *****************/
    public static Response getSync(String url) throws IOException {
        return getInstance().p_getSync(url);//同步GET，返回Response类型数据
    }


    public static String getSyncAsString(String url) throws IOException {
        return getInstance().p_getSyncAsString(url);//同步GET，返回String类型数据
    }

    public static void getAsync(String url, DataCallBack callBack) {
        getInstance().p_getAsync(url, callBack);//异步GET请求
    }

	public static void AddCookie(String url, String cookie, DataCallBack callBack) {
        getInstance().setCookic(url,cookie,callBack);
    }

    public static void postAsync(String url, Map<String, String> params, DataCallBack callBack) {
        getInstance().p_postAsync(url, params, callBack);//异步POST请求
    }
	public static void postAsyncCookie(String url,String cookie, Map<Object, Object> params, DataCallBack callBack) {
        getInstance().p_postAsyncCookie(url,cookie, params, callBack);//普通异步POST请求 设置cookie
    }
	public static void postAsyncFile(String url,String cookie, Map<String, String> params,Map<String, File> Fileparams, DataCallBack callBack) {
        getInstance().p_postAsyncFile(url,cookie, params,Fileparams, callBack);//异步POST请求带文件上传
    }
	public static void postDownLoadFile( String fileUrl, String cookie, String destFileDir, DataCallBack callBack) {
        getInstance().p_postDownLoadFile(fileUrl,cookie, destFileDir, callBack);					//异步POST请求文件下载
    }

    /**
     * 数据回调接口
     */
    public interface DataCallBack {
        void requestFailure(Call call, IOException e);

        void requestSuccess(String result);
    }

}